import axios, { AxiosInstance, AxiosRequestConfig, AxiosResponse, AxiosError } from 'axios'
import { ElMessage, ElMessageBox } from 'element-plus'
import { useUserStore } from '@/stores/user'
import router from '@/router'

// 创建axios实例
const service: AxiosInstance = axios.create({
  baseURL: import.meta.env.VITE_API_BASE_URL || '/api', // 从环境变量获取API基础URL
  timeout: 15000, // 请求超时时间
  headers: {
    'Content-Type': 'application/json;charset=utf-8'
  }
})

// 请求拦截器
service.interceptors.request.use(
  (config: AxiosRequestConfig) => {
    // 在发送请求之前做些什么
    
    // 添加token到请求头
    const userStore = useUserStore()
    if (userStore.token) {
      config.headers = {
        ...config.headers,
        'Authorization': `Bearer ${userStore.token}`
      }
    }
    
    // 添加时间戳防止缓存
    if (config.method?.toLowerCase() === 'get') {
      config.params = {
        ...config.params,
        _t: Date.now()
      }
    }
    
    // 显示loading（可选）
    if (config.showLoading !== false) {
      // 这里可以添加全局loading状态管理
      console.log('Request started:', config.url)
    }
    
    return config
  },
  (error: AxiosError) => {
    // 对请求错误做些什么
    console.error('Request error:', error)
    return Promise.reject(error)
  }
)

// 响应拦截器
service.interceptors.response.use(
  (response: AxiosResponse) => {
    // 对响应数据做点什么
    
    const { data, status, config } = response
    
    // 隐藏loading
    if (config.showLoading !== false) {
      console.log('Request completed:', config.url)
    }
    
    // 处理业务状态码
    if (data.code !== undefined) {
      // 如果后端返回了业务状态码
      if (data.code === 200 || data.code === 0) {
        return data
      } else {
        // 业务错误处理
        const errorMessage = data.message || '请求失败'
        ElMessage.error(errorMessage)
        return Promise.reject(new Error(errorMessage))
      }
    }
    
    // 如果没有业务状态码，直接返回数据
    return data
  },
  (error: AxiosError) => {
    // 对响应错误做点什么
    
    const { response, config } = error
    
    // 隐藏loading
    if (config?.showLoading !== false) {
      console.log('Request failed:', config?.url)
    }
    
    if (response) {
      // 服务器返回了错误状态码
      const { status, data } = response
      
      switch (status) {
        case 400:
          ElMessage.error('请求参数错误')
          break
        case 401:
          // 未授权，清除用户信息并跳转到登录页
          handleUnauthorized()
          break
        case 403:
          ElMessage.error('没有权限访问该资源')
          break
        case 404:
          ElMessage.error('请求的资源不存在')
          break
        case 500:
          ElMessage.error('服务器内部错误')
          break
        case 502:
          ElMessage.error('网关错误')
          break
        case 503:
          ElMessage.error('服务不可用')
          break
        case 504:
          ElMessage.error('网关超时')
          break
        default:
          ElMessage.error(`请求失败: ${status}`)
      }
      
      // 返回错误信息
      const errorMessage = (data as any)?.message || `HTTP ${status} 错误`
      return Promise.reject(new Error(errorMessage))
    } else if (error.request) {
      // 请求已发出但没有收到响应
      if (error.code === 'ECONNABORTED') {
        ElMessage.error('请求超时，请检查网络连接')
      } else {
        ElMessage.error('网络错误，请检查网络连接')
      }
      return Promise.reject(new Error('网络错误'))
    } else {
      // 其他错误
      ElMessage.error('请求配置错误')
      return Promise.reject(error)
    }
  }
)

// 处理未授权的情况
const handleUnauthorized = async () => {
  const userStore = useUserStore()
  
  try {
    await ElMessageBox.confirm(
      '登录已过期，请重新登录',
      '提示',
      {
        confirmButtonText: '重新登录',
        cancelButtonText: '取消',
        type: 'warning'
      }
    )
    
    // 清除用户信息
    userStore.logout()
    
    // 跳转到登录页
    router.push('/login')
  } catch {
    // 用户取消，不做处理
  }
}

// 封装GET请求
export const get = <T = any>(url: string, params?: any, config?: AxiosRequestConfig): Promise<T> => {
  return service.get(url, { params, ...config })
}

// 封装POST请求
export const post = <T = any>(url: string, data?: any, config?: AxiosRequestConfig): Promise<T> => {
  return service.post(url, data, config)
}

// 封装PUT请求
export const put = <T = any>(url: string, data?: any, config?: AxiosRequestConfig): Promise<T> => {
  return service.put(url, data, config)
}

// 封装DELETE请求
export const del = <T = any>(url: string, config?: AxiosRequestConfig): Promise<T> => {
  return service.delete(url, config)
}

// 封装PATCH请求
export const patch = <T = any>(url: string, data?: any, config?: AxiosRequestConfig): Promise<T> => {
  return service.patch(url, data, config)
}

// 封装上传文件请求
export const upload = <T = any>(url: string, file: File, config?: AxiosRequestConfig): Promise<T> => {
  const formData = new FormData()
  formData.append('file', file)
  
  return service.post(url, formData, {
    headers: {
      'Content-Type': 'multipart/form-data'
    },
    ...config
  })
}

// 封装下载文件请求
export const download = (url: string, params?: any, filename?: string): Promise<void> => {
  return service.get(url, {
    params,
    responseType: 'blob'
  }).then((response: any) => {
    const blob = new Blob([response])
    const downloadUrl = window.URL.createObjectURL(blob)
    const link = document.createElement('a')
    link.href = downloadUrl
    link.download = filename || 'download'
    document.body.appendChild(link)
    link.click()
    document.body.removeChild(link)
    window.URL.revokeObjectURL(downloadUrl)
  })
}

// 导出axios实例，以便需要时直接使用
export default service
